home *** CD-ROM | disk | FTP | other *** search
/ Sprite 1984 - 1993 / Sprite 1984 - 1993.iso / src / cmds / as / dist / atof-ns32k.c < prev    next >
Encoding:
C/C++ Source or Header  |  1989-09-14  |  12.3 KB  |  439 lines

  1. /* atof_ns32k.c - turn a Flonum into a ns32k floating point number
  2.    Copyright (C) 1987 Free Software Foundation, Inc.
  3.  
  4. This file is part of GAS, the GNU Assembler.
  5.  
  6. GAS is free software; you can redistribute it and/or modify
  7. it under the terms of the GNU General Public License as published by
  8. the Free Software Foundation; either version 1, or (at your option)
  9. any later version.
  10.  
  11. GAS is distributed in the hope that it will be useful,
  12. but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. GNU General Public License for more details.
  15.  
  16. You should have received a copy of the GNU General Public License
  17. along with GAS; see the file COPYING.  If not, write to
  18. the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
  19.  
  20. /* this is atof-m68k.c hacked for ns32k */
  21.  
  22. #include "as.h"
  23. #include "flonum.h"
  24.  
  25. extern FLONUM_TYPE generic_floating_point_number; /* Flonums returned here. */
  26. #define NULL (0)
  27.  
  28. extern char EXP_CHARS[];
  29.                 /* Precision in LittleNums. */
  30. #define MAX_PRECISION (4)
  31. #define F_PRECISION (2)
  32. #define D_PRECISION (4)
  33.  
  34.                 /* Length in LittleNums of guard bits. */
  35. #define GUARD (2)
  36.  
  37. int                /* Number of chars in flonum type 'letter'. */
  38. atof_sizeof (letter)
  39.      char letter;
  40. {
  41.   int    return_value;
  42.  
  43.   /*
  44.    * Permitting uppercase letters is probably a bad idea.
  45.    * Please use only lower-cased letters in case the upper-cased
  46.    * ones become unsupported!
  47.    */
  48.   switch (letter)
  49.     {
  50.     case 'f':
  51.       return_value = F_PRECISION;
  52.       break;
  53.  
  54.     case 'd':
  55.       return_value = D_PRECISION;
  56.       break;
  57.  
  58.     default:
  59.       return_value = 0;
  60.       break;
  61.     }
  62.   return (return_value);
  63. }
  64.  
  65. static unsigned long int mask [] = {
  66.   0x00000000,
  67.   0x00000001,
  68.   0x00000003,
  69.   0x00000007,
  70.   0x0000000f,
  71.   0x0000001f,
  72.   0x0000003f,
  73.   0x0000007f,
  74.   0x000000ff,
  75.   0x000001ff,
  76.   0x000003ff,
  77.   0x000007ff,
  78.   0x00000fff,
  79.   0x00001fff,
  80.   0x00003fff,
  81.   0x00007fff,
  82.   0x0000ffff,
  83.   0x0001ffff,
  84.   0x0003ffff,
  85.   0x0007ffff,
  86.   0x000fffff,
  87.   0x001fffff,
  88.   0x003fffff,
  89.   0x007fffff,
  90.   0x00ffffff,
  91.   0x01ffffff,
  92.   0x03ffffff,
  93.   0x07ffffff,
  94.   0x0fffffff,
  95.   0x1fffffff,
  96.   0x3fffffff,
  97.   0x7fffffff,
  98.   0xffffffff
  99.   };
  100.  
  101. static int bits_left_in_littlenum;
  102. static int littlenums_left;
  103. static LITTLENUM_TYPE *    littlenum_pointer;
  104.  
  105. static int
  106. next_bits (number_of_bits)
  107.      int        number_of_bits;
  108. {
  109.   int            return_value;
  110.  
  111.   if(!littlenums_left)
  112.       return 0;
  113.   if (number_of_bits >= bits_left_in_littlenum)
  114.     {
  115.       return_value  = mask [bits_left_in_littlenum] & *littlenum_pointer;
  116.       number_of_bits -= bits_left_in_littlenum;
  117.       return_value <<= number_of_bits;
  118.       if(littlenums_left) {
  119.           bits_left_in_littlenum = LITTLENUM_NUMBER_OF_BITS - number_of_bits;
  120.           littlenum_pointer --;
  121.           --littlenums_left;
  122.           return_value |= (*littlenum_pointer>>bits_left_in_littlenum) & mask[number_of_bits];
  123.       }
  124.     }
  125.   else
  126.     {
  127.       bits_left_in_littlenum -= number_of_bits;
  128.       return_value = mask [number_of_bits] & (*littlenum_pointer>>bits_left_in_littlenum);
  129.     }
  130.   return (return_value);
  131. }
  132.  
  133. static void
  134. make_invalid_floating_point_number (words)
  135.      LITTLENUM_TYPE *    words;
  136. {
  137.     words[0]= ((unsigned)-1)>>1;    /* Zero the leftmost bit */
  138.     words[1]= -1;
  139.     words[2]= -1;
  140.     words[3]= -1;
  141. }
  142.  
  143. /***********************************************************************\
  144. *                                    *
  145. *    Warning: this returns 16-bit LITTLENUMs, because that is    *
  146. *    what the VAX thinks in. It is up to the caller to figure    *
  147. *    out any alignment problems and to conspire for the bytes/word    *
  148. *    to be emitted in the right order. Bigendians beware!        *
  149. *                                    *
  150. \***********************************************************************/
  151.  
  152. char *                /* Return pointer past text consumed. */
  153. atof_ns32k (str, what_kind, words)
  154.      char *        str;    /* Text to convert to binary. */
  155.      char        what_kind; /* 'd', 'f', 'g', 'h' */
  156.      LITTLENUM_TYPE *    words;    /* Build the binary here. */
  157. {
  158.     FLONUM_TYPE    f;
  159.     LITTLENUM_TYPE    bits [MAX_PRECISION + MAX_PRECISION + GUARD];
  160.                 /* Extra bits for zeroed low-order bits. */
  161.                 /* The 1st MAX_PRECISION are zeroed, */
  162.                 /* the last contain flonum bits. */
  163.     char *        return_value;
  164.     int        precision; /* Number of 16-bit words in the format. */
  165.     long int    exponent_bits;
  166.  
  167.     long int    exponent_1;
  168.     long int    exponent_2;
  169.     long int    exponent_3;
  170.     long int    exponent_4;
  171.     int        exponent_skippage;
  172.     LITTLENUM_TYPE    word1;
  173.     LITTLENUM_TYPE *    lp;
  174.  
  175.     return_value = str;
  176.     f.low    = bits + MAX_PRECISION;
  177.     f.high    = NULL;
  178.     f.leader    = NULL;
  179.     f.exponent    = NULL;
  180.     f.sign    = '\0';
  181.  
  182.                 /* Use more LittleNums than seems */
  183.                 /* necessary: the highest flonum may have */
  184.                 /* 15 leading 0 bits, so could be useless. */
  185.  
  186.     bzero (bits, sizeof(LITTLENUM_TYPE) * MAX_PRECISION);
  187.  
  188.     switch(what_kind) {
  189.     case 'f':
  190.         precision = F_PRECISION;
  191.         exponent_bits = 8;
  192.         break;
  193.  
  194.     case 'd':
  195.         precision = D_PRECISION;
  196.         exponent_bits = 11;
  197.         break;
  198.  
  199.     default:
  200.         make_invalid_floating_point_number (words);
  201.         return NULL;
  202.     }
  203.  
  204.     f.high = f.low + precision - 1 + GUARD;
  205.  
  206.     if (atof_generic (& return_value, ".", EXP_CHARS, & f)) {
  207.         as_warn("Error converting floating point number (Exponent overflow?)");
  208.         make_invalid_floating_point_number (words);
  209.         return NULL;
  210.     }
  211.  
  212.     if (f.low > f.leader) {
  213.         /* 0.0e0 seen. */
  214.         bzero (words, sizeof(LITTLENUM_TYPE) * precision);
  215.         return return_value;
  216.     }
  217.  
  218.     if(f.sign!='+' && f.sign!='-') {
  219.         make_invalid_floating_point_number(words);
  220.         return NULL;
  221.     }
  222.  
  223.  
  224.         /*
  225.          * All vaxen floating_point formats (so far) have:
  226.          * Bit 15 is sign bit.
  227.          * Bits 14:n are excess-whatever exponent.
  228.          * Bits n-1:0 (if any) are most significant bits of fraction.
  229.          * Bits 15:0 of the next word are the next most significant bits.
  230.          * And so on for each other word.
  231.          *
  232.          * So we need: number of bits of exponent, number of bits of
  233.          * mantissa.
  234.          */
  235.     bits_left_in_littlenum = LITTLENUM_NUMBER_OF_BITS;
  236.     littlenum_pointer = f.leader;
  237.     littlenums_left = 1 + f.leader-f.low;
  238.     /* Seek (and forget) 1st significant bit */
  239.     for (exponent_skippage = 0;! next_bits(1); exponent_skippage ++)
  240.         ;
  241.     exponent_1 = f.exponent + f.leader + 1 - f.low;
  242.     /* Radix LITTLENUM_RADIX, point just higher than f.leader. */
  243.     exponent_2 = exponent_1 * LITTLENUM_NUMBER_OF_BITS;
  244.     /* Radix 2. */
  245.     exponent_3 = exponent_2 - exponent_skippage;
  246.     /* Forget leading zeros, forget 1st bit. */
  247.     exponent_4 = exponent_3 + ((1 << (exponent_bits - 1)) - 2);
  248.     /* Offset exponent. */
  249.  
  250.     if (exponent_4 & ~ mask [exponent_bits]) {
  251.             /*
  252.              * Exponent overflow. Lose immediately.
  253.              */
  254.  
  255.             /*
  256.              * We leave return_value alone: admit we read the
  257.              * number, but return a floating exception
  258.              * because we can't encode the number.
  259.              */
  260.  
  261.         as_warn("Exponent overflow in floating-point number");
  262.         make_invalid_floating_point_number (words);
  263.         return return_value;
  264.     }
  265.     lp = words;
  266.  
  267.     /* Word 1. Sign, exponent and perhaps high bits. */
  268.     /* Assume 2's complement integers. */
  269.     word1 = ((exponent_4 & mask [exponent_bits]) << (15 - exponent_bits)) |
  270.  ((f.sign == '+') ? 0 : 0x8000) | next_bits (15 - exponent_bits);
  271.     * lp ++ = word1;
  272.  
  273.     /* The rest of the words are just mantissa bits. */
  274.     for (; lp < words + precision; lp++)
  275.         * lp = next_bits (LITTLENUM_NUMBER_OF_BITS);
  276.  
  277.     if (next_bits (1)) {
  278.         unsigned long int    carry;
  279.             /*
  280.              * Since the NEXT bit is a 1, round UP the mantissa.
  281.              * The cunning design of these hidden-1 floats permits
  282.              * us to let the mantissa overflow into the exponent, and
  283.              * it 'does the right thing'. However, we lose if the
  284.              * highest-order bit of the lowest-order word flips.
  285.              * Is that clear?
  286.              */
  287.  
  288.  
  289. /* #if (sizeof(carry)) < ((sizeof(bits[0]) * BITS_PER_CHAR) + 2)
  290.     Please allow at least 1 more bit in carry than is in a LITTLENUM.
  291.     We need that extra bit to hold a carry during a LITTLENUM carry
  292.     propagation. Another extra bit (kept 0) will assure us that we
  293.     don't get a sticky sign bit after shifting right, and that
  294.     permits us to propagate the carry without any masking of bits.
  295. #endif */
  296.         for (carry = 1, lp --; carry && (lp >= words); lp --) {
  297.             carry = * lp + carry;
  298.             * lp = carry;
  299.             carry >>= LITTLENUM_NUMBER_OF_BITS;
  300.         }
  301.         if ( (word1 ^ *words) & (1 << (LITTLENUM_NUMBER_OF_BITS - 1)) ) {
  302.             /* We leave return_value alone: admit we read the
  303.              * number, but return a floating exception
  304.              * because we can't encode the number.
  305.              */
  306.             make_invalid_floating_point_number (words);
  307.             return return_value;
  308.         }
  309.     }
  310.     return (return_value);
  311. }
  312.  
  313. /* This is really identical to atof_ns32k except for some details */
  314.  
  315. gen_to_words(words,precision,exponent_bits)
  316. LITTLENUM_TYPE *words;
  317. long int    exponent_bits;
  318. {
  319.     int return_value=0;
  320.  
  321.     long int    exponent_1;
  322.     long int    exponent_2;
  323.     long int    exponent_3;
  324.     long int    exponent_4;
  325.     int        exponent_skippage;
  326.     LITTLENUM_TYPE    word1;
  327.     LITTLENUM_TYPE *    lp;
  328.  
  329.     if (generic_floating_point_number.low > generic_floating_point_number.leader) {
  330.         /* 0.0e0 seen. */
  331.         bzero (words, sizeof(LITTLENUM_TYPE) * precision);
  332.         return return_value;
  333.     }
  334.  
  335.         /*
  336.          * All vaxen floating_point formats (so far) have:
  337.          * Bit 15 is sign bit.
  338.          * Bits 14:n are excess-whatever exponent.
  339.          * Bits n-1:0 (if any) are most significant bits of fraction.
  340.          * Bits 15:0 of the next word are the next most significant bits.
  341.          * And so on for each other word.
  342.          *
  343.          * So we need: number of bits of exponent, number of bits of
  344.          * mantissa.
  345.          */
  346.     bits_left_in_littlenum = LITTLENUM_NUMBER_OF_BITS;
  347.     littlenum_pointer = generic_floating_point_number.leader;
  348.     littlenums_left = 1+generic_floating_point_number.leader - generic_floating_point_number.low;
  349.     /* Seek (and forget) 1st significant bit */
  350.     for (exponent_skippage = 0;! next_bits(1); exponent_skippage ++)
  351.         ;
  352.     exponent_1 = generic_floating_point_number.exponent + generic_floating_point_number.leader + 1 -
  353.  generic_floating_point_number.low;
  354.     /* Radix LITTLENUM_RADIX, point just higher than generic_floating_point_number.leader. */
  355.     exponent_2 = exponent_1 * LITTLENUM_NUMBER_OF_BITS;
  356.     /* Radix 2. */
  357.     exponent_3 = exponent_2 - exponent_skippage;
  358.     /* Forget leading zeros, forget 1st bit. */
  359.     exponent_4 = exponent_3 + ((1 << (exponent_bits - 1)) - 2);
  360.     /* Offset exponent. */
  361.  
  362.     if (exponent_4 & ~ mask [exponent_bits]) {
  363.             /*
  364.              * Exponent overflow. Lose immediately.
  365.              */
  366.  
  367.             /*
  368.              * We leave return_value alone: admit we read the
  369.              * number, but return a floating exception
  370.              * because we can't encode the number.
  371.              */
  372.  
  373.         make_invalid_floating_point_number (words);
  374.         return return_value;
  375.     }
  376.     lp = words;
  377.  
  378.     /* Word 1. Sign, exponent and perhaps high bits. */
  379.     /* Assume 2's complement integers. */
  380.     word1 = ((exponent_4 & mask [exponent_bits]) << (15 - exponent_bits)) |
  381.  ((generic_floating_point_number.sign == '+') ? 0 : 0x8000) | next_bits (15 - exponent_bits);
  382.     * lp ++ = word1;
  383.  
  384.     /* The rest of the words are just mantissa bits. */
  385.     for (; lp < words + precision; lp++)
  386.         * lp = next_bits (LITTLENUM_NUMBER_OF_BITS);
  387.  
  388.     if (next_bits (1)) {
  389.         unsigned long int    carry;
  390.             /*
  391.              * Since the NEXT bit is a 1, round UP the mantissa.
  392.              * The cunning design of these hidden-1 floats permits
  393.              * us to let the mantissa overflow into the exponent, and
  394.              * it 'does the right thing'. However, we lose if the
  395.              * highest-order bit of the lowest-order word flips.
  396.              * Is that clear?
  397.              */
  398.  
  399.  
  400. /* #if (sizeof(carry)) < ((sizeof(bits[0]) * BITS_PER_CHAR) + 2)
  401.     Please allow at least 1 more bit in carry than is in a LITTLENUM.
  402.     We need that extra bit to hold a carry during a LITTLENUM carry
  403.     propagation. Another extra bit (kept 0) will assure us that we
  404.     don't get a sticky sign bit after shifting right, and that
  405.     permits us to propagate the carry without any masking of bits.
  406. #endif */
  407.         for (carry = 1, lp --; carry && (lp >= words); lp --) {
  408.             carry = * lp + carry;
  409.             * lp = carry;
  410.             carry >>= LITTLENUM_NUMBER_OF_BITS;
  411.         }
  412.         if ( (word1 ^ *words) & (1 << (LITTLENUM_NUMBER_OF_BITS - 1)) ) {
  413.             /* We leave return_value alone: admit we read the
  414.              * number, but return a floating exception
  415.              * because we can't encode the number.
  416.              */
  417.             make_invalid_floating_point_number (words);
  418.             return return_value;
  419.         }
  420.     }
  421.     return (return_value);
  422. }
  423.  
  424. /* This routine is a real kludge.  Someone really should do it better, but
  425.    I'm too lazy, and I don't understand this stuff all too well anyway
  426.    (JF)
  427.  */
  428. int_to_gen(x)
  429. long x;
  430. {
  431.     char buf[20];
  432.     char *bufp;
  433.  
  434.     sprintf(buf,"%ld",x);
  435.     bufp= &buf[0];
  436.     if(atof_generic(&bufp,".", EXP_CHARS, &generic_floating_point_number))
  437.         as_warn("Error converting number to floating point (Exponent overflow?)");
  438. }
  439.